﻿// (c) Copyright 2013 Mike Riedel.
// This source is subject to the Microsoft Public License (Ms-PL).
// All other rights reserved.

using System;
using System.Collections.Generic;
using System.Threading.Tasks;

namespace FreshMeat.Storage
{
   /// <summary>
   /// Provides a context within which changes are made to a <see cref="IStore{TId,TData}"/>.
   /// </summary>
   /// <typeparam name="TId">Type of ID.</typeparam>
   /// <typeparam name="TData">Type of data.</typeparam>
   public interface IStoreContext<TId, TData> : IDisposable
   {
      /// <summary>
      /// Saves data to the store.
      /// </summary>
      /// <param name="id">The ID.</param>
      /// <param name="data">The data.</param>
      /// <returns>True if the item already existed; false if it was created.</returns>
      bool Save(TId id, TData data);

      /// <summary>
      /// Saves data to the store.
      /// </summary>
      /// <param name="id">The ID.</param>
      /// <param name="data">The data.</param>
      /// <returns>True if the item already existed; false if it was created.</returns>
      Task<bool> SaveAsync(TId id, TData data);

      /// <summary>
      /// Loads data from the store.
      /// </summary>
      /// <param name="id">The ID.</param>
      /// <param name="data">The data or default{T} if it did not exist.</param>
      /// <returns>True if the data was found.</returns>
      bool Load(TId id, out TData data);

      /// <summary>
      /// Loads data from the store.
      /// </summary>
      /// <param name="id">The ID.</param>
      /// <returns>Struct indicating whether data was found and the data.</returns>
      Task<StoreLoadResult<TData>> LoadAsync(TId id);

      /// <summary>
      /// Gets all available data from the store.
      /// </summary>
      /// <returns>All available data; this may be empty if there was no data.</returns>
      IEnumerable<TData> LoadMany();

      /// <summary>
      /// Gets all available data from the store.
      /// </summary>
      /// <returns>All available data; this may be empty if there was no data.</returns>
      Task<IEnumerable<TData>> LoadManyAsync();

      /// <summary>
      /// Gets all available IDs from the store.
      /// </summary>
      /// <returns>All available IDs; this may be empty if there was no data.</returns>
      IEnumerable<TId> LoadManyIds();

      /// <summary>
      /// Gets all available IDs from the store.
      /// </summary>
      /// <returns>All available IDs; this may be empty if there was no data.</returns>
      Task<IEnumerable<TId>> LoadManyIdsAsync();

      /// <summary>
      /// Removes data from the store.
      /// </summary>
      /// <param name="id">The ID.</param>
      /// <returns>True if the data existed.</returns>
      bool Delete(TId id);

      /// <summary>
      /// Removes data from the store.
      /// </summary>
      /// <param name="id">The ID.</param>
      /// <returns>True if the data existed.</returns>
      Task<bool> DeleteAsync(TId id);
   }
}